﻿namespace WMS6.BLL
{
    using System;
    using System.Collections.Generic;
    using System.Data;
    using System.Data.Common;
    using WMS6.Common;
    using WMS6.DataEntity;
    using WMS6.DBUtility;
    using WMS6.IDAL;
    using WMS6.QueryEntity;
    using WMS6.DALFactory;

    public class TransferBLL
    {
        private static readonly ICommonMethodDA commonMethod = DataAccess.CreateCommonMethod();
        private List<string> dataBaseID;
        private static readonly ILpnDA lpnDA = DataAccess.CreateLpnDA();
        private static readonly IOwnerDA ownerDA = DataAccess.CreateOwnerDA();
        private PubParasInfo pubParasInfo;
        private static readonly ISysSettingDA sysSettingDA = DataAccess.CreateSysSettingDA();
        private static readonly ITransferDA transferDA = DataAccess.CreateTransferDA();
        private static readonly ITransferDetailDA transferDetailDA = DataAccess.CreateTransferDetailDA();

        public TransferBLL()
        {
            this.pubParasInfo = null;
        }

        public TransferBLL(string currentWH)
        {
            this.pubParasInfo = null;
            if (!string.IsNullOrEmpty(currentWH))
            {
                this.dataBaseID = commonMethod.GetDataBaseID(currentWH);
                if (this.dataBaseID == null)
                {
                    PublicMethod.GetInstance().ShowAlertMessage("C001");
                }
            }
            else
            {
                PublicMethod.GetInstance().ShowAlertMessage("C002");
            }
        }

        public TransferBLL(PubParasInfo tempPubParasInfo)
        {
            this.pubParasInfo = null;
            if (!string.IsNullOrEmpty(tempPubParasInfo.CurrentWH))
            {
                this.dataBaseID = commonMethod.GetDataBaseID(tempPubParasInfo.CurrentWH);
                if (this.dataBaseID == null)
                {
                    PublicMethod.GetInstance().ShowAlertMessage("C001", this.pubParasInfo.UserLanguage);
                }
                else
                {
                    this.pubParasInfo = new PubParasInfo();
                    this.pubParasInfo = tempPubParasInfo;
                }
            }
            else
            {
                PublicMethod.GetInstance().ShowAlertMessage("C002", this.pubParasInfo.UserLanguage);
            }
        }

        public string BatchInsertInvTransfer(TransferInfo transferInfo)
        {
            DataBase dataBase = new DataBase();
            DbConnection conn = dataBase.connection;
            conn.Open();
            DbTransaction tran = conn.BeginTransaction();
            string transferID = string.Empty;
            try
            {
                if (!ownerDA.CheckTradePartnerIDUnique(transferInfo.FromOwnerID, this.dataBaseID[0]))
                {
                    PublicMethod.GetInstance().ShowAlertMessage("F5300_001", this.pubParasInfo.UserLanguage, new List<string> { transferInfo.FromOwnerID });
                }
                else if (!commonMethod.CheckAuthorizationOwnerByUserID(this.pubParasInfo.UserID, transferInfo.FromOwnerID))
                {
                    PublicMethod.GetInstance().ShowAlertMessage("F5300_002", this.pubParasInfo.UserLanguage, new List<string> { transferInfo.FromOwnerID });
                }
                if (!ownerDA.CheckTradePartnerIDUnique(transferInfo.ToOwnerID, this.dataBaseID[0]))
                {
                    PublicMethod.GetInstance().ShowAlertMessage("F5300_003", this.pubParasInfo.UserLanguage, new List<string> { transferInfo.ToOwnerID });
                }
                else if (!commonMethod.CheckAuthorizationOwnerByUserID(this.pubParasInfo.UserID, transferInfo.ToOwnerID))
                {
                    PublicMethod.GetInstance().ShowAlertMessage("F5300_004", this.pubParasInfo.UserLanguage, new List<string> { transferInfo.ToOwnerID });
                }
                transferInfo.TransferID = commonMethod.GenNextNumStr(dataBase, tran, "TRANSFER", this.dataBaseID[0]);
                transferInfo.UpdatedBy = transferInfo.CreatedBy;
                transferInfo.CreatedDate = DateTime.Now;
                transferInfo.UpdatedDate = DateTime.Now;
                if (transferDA.InsertTransfer(dataBase, tran, transferInfo, this.dataBaseID[0]) > 0)
                {
                    AuditDataBLL auditDataBLL = new AuditDataBLL();
                    auditDataBLL.InsertAuditData<TransferInfo>(dataBase, tran, null, transferInfo, AuditAction.Insert, this.pubParasInfo.UserID, "TRANSFER", this.dataBaseID[0]);
                    SysSettingInfo sysSetting = sysSettingDA.GetSysSettingByID(dataBase, tran, "LPNWhetherToallowDuplicate", this.dataBaseID[0], this.pubParasInfo);
                    using (List<TransferDetailInfo>.Enumerator CS50002 = transferInfo.TransferDetailInfos.GetEnumerator())
                    {
                        TransferDetailInfo info;
                        while (CS50002.MoveNext())
                        {
                            info = CS50002.Current;
                            if ((sysSetting != null) && (sysSetting.Value == "N"))
                            {
                                if (lpnDA.CheckLpnIDUnique(dataBase, tran, info.ToLpnID, this.dataBaseID[0]))
                                {
                                    throw new Exception("LPN已经存在,请重新输入!");
                                }
                                if (transferInfo.TransferDetailInfos.FindAll(x => x.ToLpnID == info.ToLpnID).Count > 1)
                                {
                                    throw new Exception("LPN已经存在,请重新输入!");
                                }
                            }
                            info.TransferID = transferInfo.TransferID;
                            info.UpdatedBy = info.CreatedBy;
                            info.CreatedDate = DateTime.Now;
                            info.UpdatedDate = DateTime.Now;
                            string lotID = new InboundHelper().CheckLotAttributeInfo(dataBase, tran, info.TransferLotInfo, info.ToOwnerID, info.ToSkuID, this.dataBaseID[0], info.UpdatedBy);
                            info.ToLot = lotID;
                            if (transferDetailDA.InsertTransferDetail(dataBase, tran, info, this.dataBaseID[0]) > 0)
                            {
                                auditDataBLL.InsertAuditData<TransferDetailInfo>(null, info, AuditAction.Insert, this.pubParasInfo.UserID, "TRANSFER_DETAIL", this.dataBaseID[0]);
                            }
                        }
                    }
                    transferID = transferInfo.TransferID;
                }
                tran.Commit();
            }
            catch (Exception ex)
            {
                tran.Rollback();
                CommonErrorHandler.ErrorHandler(ex, LogType.Error);
            }
            finally
            {
                conn.Close();
            }
            return transferID;
        }

        public string ExecuteInvTransfer(string transferID, List<string> lineID, string updatedBy)
        {
            string temp = string.Empty;
            string whLoginID = this.dataBaseID[0];
            DataBase dataBase = new DataBase();
            DbConnection conn = dataBase.connection;
            conn.Open();
            DbTransaction tran = conn.BeginTransaction();
            try
            {
                int i;
                List<TransferDetailInfo> tempTransferDetailInfos = transferDetailDA.GetTransferDetailListByID(dataBase, tran, transferID, whLoginID);
                List<TransferDetailInfo> transferDetailInfos = new List<TransferDetailInfo>();
                for (i = 0; i < tempTransferDetailInfos.Count; i++)
                {
                    for (int j = 0; j < lineID.Count; j++)
                    {
                        if (tempTransferDetailInfos[i].LineID.ToString() == lineID[j])
                        {
                            tempTransferDetailInfos[i].Status = TransferStatus.Confirmed;
                            transferDetailDA.ChangeTransferDetailStatus(dataBase, tran, transferID, lineID[j], TransferStatus.Confirmed, updatedBy, whLoginID);
                            transferDetailInfos.Add(tempTransferDetailInfos[i]);
                            break;
                        }
                    }
                }
                string transferStatus = this.GetTransferInfoStatus(tempTransferDetailInfos);
                transferDA.ChangeTransferStatus(dataBase, tran, transferID, transferStatus, updatedBy, whLoginID);
                TransferInfo transferInfo = transferDA.GetTransferByID(dataBase, tran, transferID, whLoginID);
                InventoryMgtBLL inventoryMgtBLL = new InventoryMgtBLL(this.pubParasInfo);
                for (i = 0; i < transferDetailInfos.Count; i++)
                {
                    InvMovesInfo invMovesInfo = new InvMovesInfo(transferDetailInfos[i].FromOwnerID, transferDetailInfos[i].FromSkuID, transferDetailInfos[i].FromLot, transferDetailInfos[i].FromLoc, transferDetailInfos[i].FromLpnID, transferDetailInfos[i].ToOwnerID, transferDetailInfos[i].ToSkuID, transferDetailInfos[i].ToLot, transferDetailInfos[i].ToLoc, transferDetailInfos[i].ToLpnID, transferDetailInfos[i].ToQty, transferDetailInfos[i].ToPackID, transferDetailInfos[i].ToUomID, transferDetailInfos[i].FromQty, transferDetailInfos[i].FromPackID, transferDetailInfos[i].FromUomID, updatedBy, tempTransferDetailInfos[i].TransferID, transferDetailInfos[i].LineID);
                    inventoryMgtBLL.UpdateInvLotLocLpn4Moves(dataBase, tran, invMovesInfo, InvMoveType.Transfer, whLoginID);
                    inventoryMgtBLL.UpdateInvSkuLoc4Moves(dataBase, tran, invMovesInfo, InvMoveType.Transfer, whLoginID);
                    inventoryMgtBLL.UpdateLpn4Moves(dataBase, tran, invMovesInfo, whLoginID);
                    inventoryMgtBLL.UpdateInvLot4Moves(dataBase, tran, invMovesInfo, InvMoveType.Transfer, whLoginID);
                    invMovesInfo.MoveDate = transferInfo.TransferDate;
                    inventoryMgtBLL.InsertInvMovesTrans(dataBase, tran, invMovesInfo, TransSourceType.TransferDetailAdd, whLoginID);
                    InvMovesInfo invFromMovesInfo = new InvMovesInfo("", "", "", transferDetailInfos[i].FromLoc, transferDetailInfos[i].FromLpnID, transferDetailInfos[i].FromOwnerID, transferDetailInfos[i].FromSkuID, transferDetailInfos[i].FromLot, transferDetailInfos[i].FromLoc, transferDetailInfos[i].FromLpnID, transferDetailInfos[i].FromQty * -1M, transferDetailInfos[i].FromPackID, transferDetailInfos[i].FromUomID, transferDetailInfos[i].FromQty, transferDetailInfos[i].FromPackID, transferDetailInfos[i].FromUomID, updatedBy, transferDetailInfos[i].TransferID, transferDetailInfos[i].LineID) {
                        MoveDate = transferInfo.TransferDate
                    };
                    inventoryMgtBLL.InsertInvMovesTrans(dataBase, tran, invFromMovesInfo, TransSourceType.TransferDetailUpdate, whLoginID);
                    temp = temp + transferDetailInfos[i].LineID.ToString() + ",";
                }
                tran.Commit();
            }
            catch (Exception ex)
            {
                tran.Rollback();
                CommonErrorHandler.ErrorHandler(ex, LogType.Error);
            }
            finally
            {
                conn.Close();
            }
            return temp.Substring(0, temp.Length - 1);
        }

        public DataSet GetInvTransferInfoByQueryEntity(TransferQueryEntity transferQuery)
        {
            List<string> sqlWhere = new List<string>();
            if (!string.IsNullOrEmpty(transferQuery.TransferID))
            {
                sqlWhere.Add(" TRANSFER_ID " + transferQuery.TransferID);
            }
            if (!string.IsNullOrEmpty(transferQuery.Status))
            {
                sqlWhere.Add(" STATUS " + transferQuery.Status);
            }
            if (!string.IsNullOrEmpty(transferQuery.TransferType))
            {
                sqlWhere.Add(" TRANSFER_TYPE " + transferQuery.TransferType);
            }
            return transferDA.GetTransferByQueryList(sqlWhere, transferQuery, this.dataBaseID[0]);
        }

        public TransferInfo GetTransferInfoByID(string transferID)
        {
            TransferInfo transfer = transferDA.GetTransferByID(transferID, this.dataBaseID[0]);
            if (transfer != null)
            {
                transfer.TransferDetailInfos = transferDetailDA.GetTransferDetailListByID(transferID, this.dataBaseID[0]);
            }
            return transfer;
        }

        private string GetTransferInfoStatus(List<TransferDetailInfo> transferDetailInfos)
        {
            int totalCount = 0;
            for (int i = 0; i < transferDetailInfos.Count; i++)
            {
                if (transferDetailInfos[i].Status == TransferStatus.Confirmed)
                {
                    totalCount++;
                }
            }
            if (totalCount == transferDetailInfos.Count)
            {
                return TransferStatus.Confirmed;
            }
            return TransferStatus.New;
        }

        public string InsertTransferInfo(TransferInfo transferInfo)
        {
            DataBase dataBase = new DataBase();
            DbConnection conn = dataBase.connection;
            conn.Open();
            DbTransaction tran = conn.BeginTransaction();
            string transferID = string.Empty;
            try
            {
                if (!ownerDA.CheckTradePartnerIDUnique(transferInfo.FromOwnerID, this.dataBaseID[0]))
                {
                    PublicMethod.GetInstance().ShowAlertMessage("F5300_001", this.pubParasInfo.UserLanguage, new List<string> { transferInfo.FromOwnerID });
                }
                else if (!commonMethod.CheckAuthorizationOwnerByUserID(this.pubParasInfo.UserID, transferInfo.FromOwnerID))
                {
                    PublicMethod.GetInstance().ShowAlertMessage("F5300_002", this.pubParasInfo.UserLanguage, new List<string> { transferInfo.FromOwnerID });
                }
                if (!ownerDA.CheckTradePartnerIDUnique(transferInfo.ToOwnerID, this.dataBaseID[0]))
                {
                    PublicMethod.GetInstance().ShowAlertMessage("F5300_003", this.pubParasInfo.UserLanguage, new List<string> { transferInfo.ToOwnerID });
                }
                else if (!commonMethod.CheckAuthorizationOwnerByUserID(this.pubParasInfo.UserID, transferInfo.ToOwnerID))
                {
                    PublicMethod.GetInstance().ShowAlertMessage("F5300_004", this.pubParasInfo.UserLanguage, new List<string> { transferInfo.ToOwnerID });
                }
                transferInfo.TransferID = commonMethod.GenNextNumStr(dataBase, tran, "TRANSFER", this.dataBaseID[0]);
                transferInfo.UpdatedBy = transferInfo.CreatedBy;
                transferInfo.CreatedDate = DateTime.Now;
                transferInfo.UpdatedDate = DateTime.Now;
                if (transferDA.InsertTransfer(dataBase, tran, transferInfo, this.dataBaseID[0]) > 0)
                {
                    new AuditDataBLL().InsertAuditData<TransferInfo>(dataBase, tran, null, transferInfo, AuditAction.Insert, this.pubParasInfo.UserID, "TRANSFER", this.dataBaseID[0]);
                    transferID = transferInfo.TransferID;
                }
                tran.Commit();
            }
            catch (Exception ex)
            {
                tran.Rollback();
                CommonErrorHandler.ErrorHandler(ex, LogType.Error);
            }
            finally
            {
                conn.Close();
            }
            return transferID;
        }
    }
}

